package com.ruoyi.combat.service.antihoming.impl;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONUtil;
import com.ruoyi.combat.config.Neo4jConfig;
import com.ruoyi.combat.config.PredictAntiHomingInfoTask;
import com.ruoyi.combat.domain.CombatAtlasNewTask;
import com.ruoyi.combat.domain.neo4j.*;
import com.ruoyi.combat.domain.request.AntiHomingInfoRequest;
import com.ruoyi.combat.mapper.CombatAtlasTaskMapper;
import com.ruoyi.combat.repository.*;
import com.ruoyi.combat.service.antihoming.AntiHomingInfoService;
import com.ruoyi.combat.service.antihoming.CombatAtlasTaskService;
import com.ruoyi.combat.service.externalServiceInvoker.AntiIpHomingService;
import com.ruoyi.combat.util.MethodUseUtils;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.system.domain.SysConfig;
import com.ruoyi.system.mapper.SysConfigMapper;
import lombok.extern.slf4j.Slf4j;
import okhttp3.*;
import org.neo4j.driver.Record;
import org.neo4j.driver.Result;
import org.neo4j.driver.types.Node;
import org.neo4j.driver.types.Path;
import org.neo4j.driver.types.Relationship;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageImpl;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.io.IOException;
import java.math.BigDecimal;
import java.util.*;
import java.util.stream.Collectors;

@Service
@Slf4j
public class AntiHomingInfoServiceImpl implements AntiHomingInfoService {

//    private static final Logger log = LoggerFactory.getLogger(AntiHomingInfoServiceImpl.class);

    @Autowired
    private IpNodeRepository ipNodeRepository;
    @Autowired
    private OrgNodeRepository orgNodeRepository;
    @Autowired
    private AntiIpHomingService antiIpHomingService;
    @Autowired
    private CombatAtlasTaskService combatAtlasTaskService;
    @Autowired
    private ForecastOrgNodeRepository forecastOrgNodeRepository;
    @Autowired
    private SysConfigMapper sysConfigMapper;

    @Autowired
    private MethodUseUtils methodUseUtils;
    @Autowired
    private CombatAtlasTaskMapper combatAtlasTaskMapper;
    @Autowired
    private Neo4jConfig neo4jConfig;

    /**
     * 分页查询neo4j中的图谱数据
     *
     * @param request
     */
    @Override
    public Page<IpNode> antiHomingInfoByIpOrOrg(AntiHomingInfoRequest request) {
        Integer pageNum = request.getPageNum();
        Integer pageSize = request.getPageSize();
        if (pageNum == null || pageSize == null) {
            throw new RuntimeException("分页参数不能为空");
        }
        if (pageNum > 0) {
            pageNum = pageNum - 1;
        }

        Pageable pageable = PageRequest.of(pageNum, pageSize);
        // 分页查询关系图谱
        if (StrUtil.isBlank(request.getIp()) && StrUtil.isBlank(request.getOrg())) {
            Page<IpNode> relationsByPage = ipNodeRepository.findByPage(pageNum, pageSize, pageable);
            if (relationsByPage != null) {
                List<IpNode> content = relationsByPage.getContent();
                for (IpNode ipNode : content) {
                    // 根据IP地址查询Org
                    List<IpNode> orgByIps = ipNodeRepository.findOrgByIp(ipNode.getAddress());
                    if (orgByIps != null && orgByIps.size() > 0) {
                       /* if (orgByIps.size() > 1) {
                            // 删除一条关系
//                            ipNodeRepository.deleteRelationsByIpAndOrg(orgByIps.get(1).getAddress(), orgByIps.get(1).getOrg().getName());
                        }*/
                        ipNode.setOrg(orgByIps.get(0).getOrg());
                        ipNode.setCity(orgByIps.get(0).getCity());
                        ipNode.setIpc(orgByIps.get(0).getIpc());
                    }
                    // 根据IP地址查询org
                    List<OrgNode> orgByIpNew = orgNodeRepository.findOrgByIpNew(ipNode.getAddress());
                    if (orgByIpNew != null && orgByIpNew.size() > 0) {
                        ipNode.setOrg(orgByIpNew.get(0));
                    }
                   /* // 根据IP地址查询Domain
                    List<IpNode> domainByIps = ipNodeRepository.findDomainByIp(ipNode.getAddress());
                    if (domainByIps != null && domainByIps.size() > 0) {
                        ipNode.setDomain(domainByIps.get(0).getDomain());
                    }
                    // 根据IP地址查询IPC
                    IpNode ipcByIp = ipNodeRepository.findIPCByIp(ipNode.getAddress());
                    if (ipcByIp != null) {
                        ipNode.setIpc(ipcByIp.getIpc());
                    }*/
                }
            }
            return relationsByPage;
        }
        // 根据IP和组织分页查询图谱关系
        /*if (StrUtil.isNotBlank(request.getIp()) && StrUtil.isNotBlank(request.getOrg())) {
            Page<IpNode> relationsByIpAndOrg = ipNodeRepository.findRelationsByIpAndOrg(request.getIp(), request.getOrg(), pageNum, pageSize, pageable);
            if (relationsByIpAndOrg != null) {
                List<IpNode> content = relationsByIpAndOrg.getContent();
                for (IpNode ipNode : content) {
                    // 根据IP地址查询Org
                    List<IpNode> orgByIps = ipNodeRepository.findOrgByIp(ipNode.getAddress());
                    if (orgByIps != null && orgByIps.size() > 0) {
                        if (orgByIps.size() > 1) {
                            // 删除一条关系
                            ipNodeRepository.deleteRelationsByIpAndOrg(orgByIps.get(1).getAddress(), orgByIps.get(1).getOrg().getName());
                        }
                        ipNode.setOrg(orgByIps.get(0).getOrg());
                    }
                    // 根据IP地址查询City
                    IpNode cityByIp = ipNodeRepository.findCityByIp(ipNode.getAddress());
                    if (cityByIp != null) {
                        ipNode.setCity(cityByIp.getCity());
                    }
                    // 根据IP地址查询Domain
                    List<IpNode> domainByIps = ipNodeRepository.findDomainByIp(ipNode.getAddress());
                    if (domainByIps != null && domainByIps.size() > 0) {
                        ipNode.setDomain(domainByIps.get(0).getDomain());
                    }
                    // 根据IP地址查询IPC
                    IpNode ipcByIp = ipNodeRepository.findIPCByIp(ipNode.getAddress());
                    if (ipcByIp != null) {
                        ipNode.setIpc(ipcByIp.getIpc());
                    }
                }
            }
            return relationsByIpAndOrg;
        }*/
        // 根据IP分页查询图谱关系
        if (StrUtil.isNotBlank(request.getIp())) {
            Page<IpNode> relationsByIp = ipNodeRepository.findIPNodeByIp(request.getIp(), pageNum, pageSize, pageable);
            if (relationsByIp != null) {
                List<IpNode> content = relationsByIp.getContent();
                for (IpNode ipNode : content) {
                    List<IpNode> orgByIps = ipNodeRepository.findOrgByIp(ipNode.getAddress());
                    if (orgByIps != null && orgByIps.size() > 0) {
                        ipNode.setCity(orgByIps.get(0).getCity());
                        ipNode.setIpc(orgByIps.get(0).getIpc());
                    }
                    // 根据IP地址查询org
                    List<OrgNode> orgByIpNew = orgNodeRepository.findOrgByIpNew(ipNode.getAddress());
                    if (orgByIpNew != null && orgByIpNew.size() > 0) {
                        ipNode.setOrg(orgByIpNew.get(0));
                    }
                }
            }
            return relationsByIp;
        }
        // 根据组织分页查询图谱关系
        if (StrUtil.isNotBlank(request.getOrg())) {
            Page<IpNode> relationsByOrg = ipNodeRepository.findIpByAttackability(request.getOrg(), pageNum, pageSize, pageable);
            if (relationsByOrg != null) {
                List<IpNode> content = relationsByOrg.getContent();
                for (IpNode ipNode : content) {
                    List<IpNode> orgByIps = ipNodeRepository.findOrgByIp(ipNode.getAddress());
                    if (orgByIps != null && orgByIps.size() > 0) {
                        ipNode.setCity(orgByIps.get(0).getCity());
                        ipNode.setIpc(orgByIps.get(0).getIpc());
                    }
                    // 根据IP地址查询org
                    List<OrgNode> orgByIpNew = orgNodeRepository.findOrgByIpNew(ipNode.getAddress());
                    if (orgByIpNew != null && orgByIpNew.size() > 0) {
                        ipNode.setOrg(orgByIpNew.get(0));
                    }
                }
            }
            return relationsByOrg;
        }
        return null;
    }

    @Override
    public List<Map> riskPageQuery(AntiHomingInfoRequest request) {
        /*Integer pageNum = request.getPageNum();
        Integer pageSize = request.getPageSize();
        if (pageNum == null || pageSize == null) {
            throw new RuntimeException("分页参数不能为空");
        }
        if (pageNum > 0) {
            pageNum = pageNum - 1;
        }
        Pageable pageable = PageRequest.of(pageNum, pageSize);
        Page<IpNode> belongs_to = ipNodeRepository.findIpByAttackability(pageNum, pageSize, pageable);*/



        /*if (belongs_to != null) {
            List<IpNode> content = belongs_to.getContent();
            for (IpNode ipNode : content) {
                List<IpNode> orgByIps = ipNodeRepository.findOrgByIp(ipNode.getAddress());
                if (orgByIps != null && orgByIps.size() > 0) {
                    ipNode.setCity(orgByIps.get(0).getCity());
                    ipNode.setIpc(orgByIps.get(0).getIpc());
                }
                // 根据IP地址查询org
                List<OrgNode> orgByIpNew = orgNodeRepository.findOrgByIpNew(ipNode.getAddress());
                if (orgByIpNew != null && orgByIpNew.size() > 0) {
                    ipNode.setOrg(orgByIpNew.get(0));
                }
            }
        }*/

        String cypher = "MATCH (ip:Ip {CanAttack: 1})<-[*1..3]-(o:Org) return ip, o";
        Result run = neo4jConfig.run(cypher);
        List<Record> list = run.list();
        List<Map> listdata = new ArrayList<>();
        Map<String, Object> ipdata = new HashMap<>();
        list.forEach(record -> {
            List<String> keys = record.keys();
            Map<String, Object> data = new HashMap<>();
            IpNode ipNode = new IpNode();
            OrgNode orgNode = new OrgNode();
            String IP = "";
            Node node = record.get("ip").asNode();
            IP = node.get("Ip").asString();
            ipNode.setId(node.id());
            ipNode.setAddress(IP);
            Node node1 = record.get("o").asNode();
            orgNode.setId(node1.id());
            orgNode.setName(node1.get("name").asString());
            if (ipdata.get(IP) != null) {
                return;
            }
            ipdata.put(IP, ipNode);
            data.put("ip", ipNode);
            data.put("o", orgNode);
            listdata.add(data);
        });
        return listdata;
    }


    @Override
    public List<Map> predictRelationship(AntiHomingInfoRequest request) {
        /*Integer pageNum = request.getPageNum();
        Integer pageSize = request.getPageSize();
        if (pageNum == null || pageSize == null) {
            throw new RuntimeException("分页参数不能为空");
        }
        if (pageNum > 0) {
            pageNum = pageNum - 1;
        }
        Pageable pageable = PageRequest.of(pageNum, pageSize);
        Page<IpNode> belongs_to = ipNodeRepository.findIpByPredictable(pageNum, pageSize, pageable);
        if (belongs_to != null) {
            List<IpNode> content = belongs_to.getContent();
            for (IpNode ipNode : content) {
                List<IpNode> orgByIps = ipNodeRepository.findOrgByIp(ipNode.getAddress());
                if (orgByIps != null && orgByIps.size() > 0) {
                    ipNode.setCity(orgByIps.get(0).getCity());
                    ipNode.setIpc(orgByIps.get(0).getIpc());
                }
                // 根据IP地址查询org
                List<OrgNode> orgByIpNew = orgNodeRepository.findOrgByIpNew(ipNode.getAddress());
                if (orgByIpNew != null && orgByIpNew.size() > 0) {
                    ipNode.setOrg(orgByIpNew.get(0));
                }
            }
        }
        return belongs_to;*/

        String cypher = "MATCH (start_ip:Ip {analyzable: 1})-[:BELONGS_TO]->(ipc:IpC) MATCH (ipc)<-[:BELONGS_TO]-(landmark_ip:Ip) WHERE landmark_ip.landmark_node = 1 MATCH path = (landmark_ip)<-[*1..3]-(o:Org) RETURN start_ip, o";
        Result run = neo4jConfig.run(cypher);
        List<Record> list = run.list();
        List<Map> listdata = new ArrayList<>();
        Map<String, Object> ipdata = new HashMap<>();
        list.forEach(record -> {
            List<String> keys = record.keys();
            Map<String, Object> data = new HashMap<>();
            IpNode ipNode = new IpNode();
            OrgNode orgNode = new OrgNode();
            String IP = "";
            Node node = record.get("start_ip").asNode();
            IP = node.get("Ip").asString();
            ipNode.setId(node.id());
            ipNode.setAddress(IP);
            Node node1 = record.get("o").asNode();
            orgNode.setId(node1.id());
            orgNode.setName(node1.get("name").asString());
            if (ipdata.get(IP) != null) {
                return;
            }
            ipdata.put(IP, ipNode);
            data.put("ip", ipNode);
            data.put("o", orgNode);
            listdata.add(data);
        });
        return listdata;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void antiHomingInfo(AntiHomingInfoRequest request) {
        if (StrUtil.isBlank(request.getIp()) || StrUtil.isBlank(request.getOrg()) || StrUtil.isBlank(request.getFantype())) {
            throw new RuntimeException("ip、组织、抗归属方法不能为空");
        }
        try {
            CombatAtlasTask task = new CombatAtlasTask();
            task.setTargetIp(request.getIp());
            task.setTaskMethod("1");
            task.setType("1");
            task.setTaskStatus("1");
            task.setStartTime(DateUtils.getTime());
            task.setBeforeRiskOrg(request.getOrg());
            task.setAfterRiskOrg(request.getNewOrg());
            combatAtlasTaskService.insertCombatAtlasTask(task);
            SysConfig sysConfig = sysConfigMapper.selectConfigById(8L);
            if ("true".equals(sysConfig.getConfigValue())) {
                // 调用确定抗归属算法
                antiIpHomingService.antiIpHoming(request.getIp(), request.getOrg(), request.getNewOrg(), request.getFantype());
            } else {

            }
        } catch (Exception e) {
            log.error(e.getMessage(), e);
            throw new RuntimeException("抗定位失败");
        }
    }


    public String getResult(String ip, String type) {
        String cql = "MATCH (start_ip:Ip {Ip: '" + ip + "'})-[:BELONGS_TO]->(ipc:IpC) MATCH (ipc)<-[:BELONGS_TO]-(landmark_ip:Ip) WHERE landmark_ip.landmark_node = 1 MATCH path = (landmark_ip)<-[*1..3]-(o:Org) RETURN start_ip, ipc, landmark_ip, o,[node IN nodes(path) | node] as all_nodes_in_path, [rel IN relationships(path) | rel] as all_relationships_in_path, length(path) as path_length";
        Result run = neo4jConfig.run(cql, type);
        List<Record> list = run.list();
        List<Map> listdata = new ArrayList<>();
        list.forEach(record -> {
            List<String> keys = record.keys();
            Map<String, Object> data = new HashMap<>();
            keys.forEach(key -> {
                if ("start_ip".equals(key)) {
                    Node node = record.get(key).asNode();
                    IpNode ipNode = new IpNode();
                    ipNode.setId(node.id());
                    ipNode.setAddress(node.get("Ip").asString());
                    data.put(key, ipNode);
                } else if ("ipc".equals(key)) {
                    Node node = record.get(key).asNode();
                    IpcNode ipcNode = new IpcNode();
                    ipcNode.setId(node.id());
                    ipcNode.setName(node.get("IpC").asString());
                    data.put(key, ipcNode);
                } else if ("landmark_ip".equals(key)) {
                    org.neo4j.driver.Value value = record.get(key);
                    Map map = new HashMap();
                    map.put("id", value.asNode().id());
                    map.put("labels", value.asNode().labels());
                    map.put("value", value.asNode().asMap());
                } else if ("o".equals(key)) {
                    org.neo4j.driver.Value value = record.get(key);
                    Map map = new HashMap();
                    map.put("id", value.asNode().id());
                    map.put("labels", value.asNode().labels());
                    map.put("value", value.asNode().asMap());
                } else if ("all_nodes_in_path".equals(key)) {
                    List<Map> pathList = new ArrayList<>();
                    List<Node> list1 = record.get(key).asList(value -> value.asNode());
                    list1.forEach(node -> {
                        Map map = new HashMap();
                        Iterable<String> labels = node.labels();
                        map.put("labels", labels);
                        map.put("value", node.asMap());
                        map.put("id", node.id());
                        pathList.add(map);
                    });
                    data.put(key, pathList);

                } else if ("all_relationships_in_path".equals(key)) {
                    List<Map> pathList = new ArrayList<>();
                    List<Relationship> list1 = record.get(key).asList(value -> value.asRelationship());
                    list1.forEach(node -> {
                        Map map = new HashMap();
                        map.put("type", node.type());
                        map.put("start", node.startNodeId());
                        map.put("end", node.endNodeId());
                        map.put("value", node.asMap());
                        map.put("id", node.id());
                        pathList.add(map);
                    });
                    data.put(key, pathList);

                } else if ("path_length".equals(key)) {
                    int string = record.get(key).asInt();
                    data.put(key, string);
                }
            });
            listdata.add(data);
        });
        return JSONUtil.toJsonStr(listdata);
    }


    @Override
    @Transactional(rollbackFor = Exception.class)
    public Map<String, Object> predictAntiHomingInfo(AntiHomingInfoRequest request) {

        if (StrUtil.isBlank(request.getIp())) {

            throw new RuntimeException("ip不能为空");
        }

        Map<String, Object> result = new HashMap<>();
        try {
            String ip = request.getIp();
            CombatAtlasNewTask task = new CombatAtlasNewTask();
            task.setIp(ip);
            task.setMethod("2");
            task.setType("2");
            task.setStartTime(new Date());
            task.setStatus("1");

            String result1 = getResult(ip, "1");
            task.setBefor(result1);
            combatAtlasTaskMapper.insertCombatAtlasTask(task);
            Map<String, Object> data = new HashMap<>();
            data.put("ip_address", ip);
            String jsonStr = JSONUtil.toJsonStr(data);
            result = methodUseUtils.methodUseLogs(54l, jsonStr);
            task.setStatus("2");
            task.setContent(JSONUtil.toJsonStr(result));

            task.setEndTime(new Date());
            combatAtlasTaskMapper.updateCombatAtlasTask(task);

            new Thread(new PredictAntiHomingInfoTask(ip, task, combatAtlasTaskMapper, neo4jConfig)).start();


            /*log.info("第一步请求数据：{}", jsonStr);
            Map<String, Object> stringObjectMap = methodUseUtils.methodUseLogs(51l, jsonStr);
            log.info("第一步请求返回数据：{}", JSONUtil.toJsonStr(stringObjectMap));
            if (stringObjectMap != null && stringObjectMap.get("node_count") != null) {
                String s = String.valueOf(stringObjectMap.get("node_count"));
                if (Integer.parseInt(s) <= 0) {
                    throw new RuntimeException("没有这个节点");
                }
                List list = new ArrayList<>();
                list.add(ip);
                jsonStr = JSONUtil.toJsonStr(list);

                log.info("第二步请求数据：{}", jsonStr);
                List<Map> stringObjectMap1 = methodUseUtils.methodUse(52l, jsonStr);
                log.info("第二步请求返回数据：{}", JSONUtil.toJsonStr(stringObjectMap1));
                if (stringObjectMap1 != null && stringObjectMap1.size() > 0) {
                    Map map1 = stringObjectMap1.get(0);
                    String jsonStr1 = JSONUtil.toJsonStr(map1.get("org_probabilities"));
                    List<Map> list1 = JSONUtil.toList(jsonStr1, Map.class);
                    if (list1.size() == 1) {
                        List<OrgNode> all = orgNodeRepository.findAll();
                        Random random = new Random(all.size() - 1);
                        int i = random.nextInt();
                        OrgNode orgNode = all.get(i);
                        Map map2 = new HashMap<>();
                        map2.put("org", orgNode.getName());
                        map2.put("prob", "0.91");
                        list1.add(map2);
                    }
                    Collections.sort(list1, (a, b) -> {
                        double probA = (double) a.get("prob");
                        double probB = (double) b.get("prob");
                        return Double.compare(probB, probA); // 降序
                    });
                    Map map = list1.get(0);
                    String org = (String) map.get("org");
                    log.info("org:{}", org);

                    Map map2 = list1.get(1);
                    String org2 = (String) map2.get("org");
                    log.info("org2:{}", org);


                    task.setBefor(jsonStr1);


                    Map<String, Object> data2 = new HashMap<>();

                    data2.put("ip", ip);
                    data2.put("action", "list_landmarks");
                    jsonStr = JSONUtil.toJsonStr(data2);
                    log.info("第三步请求数据：{}", jsonStr);
                    Map<String, Object> stringObjectMap2 = methodUseUtils.methodUseLogs(53l, jsonStr);
                    log.info("第三步请求返回数据：{}", JSONUtil.toJsonStr(stringObjectMap2));
                    if (stringObjectMap2 != null && stringObjectMap2.get("landmarks") != null) {
                        String jsonStr3 = JSONUtil.toJsonStr(stringObjectMap2.get("landmarks"));
                        List<List> list2 = JSONUtil.toList(jsonStr3, List.class);
                        List<String> listData = new ArrayList<>();
                        for (List li : list2) {
                            String name = String.valueOf(li.get(1));
                            if (org.equals(name)) {
                                listData.add(String.valueOf(li.get(0)));
                            }
                        }
                        Map<String, Object> data3 = new HashMap<>();
                        data3.put("ip", ip);
                        data3.put("action", "reassign_landmarks");
                        data3.put("landmark_ip", listData);
                        data3.put("new_org", org2);
                        String jsonStr2 = JSONUtil.toJsonStr(data3);
                        log.info("第四步请求数据：{}", jsonStr);
                        Map<String, Object> stringObjectMap3 = methodUseUtils.methodUseLogs(53l, jsonStr2);
                        log.info("第四步请求返回数据：{}", JSONUtil.toJsonStr(stringObjectMap3));
                        if (stringObjectMap3 != null && stringObjectMap3.get("changed") != null) {
                            //  第四步
                            Map<String, Object> data4 = new HashMap<>();
                            data4.put("ip", ip);
                            data4.put("action", "rerun_analysis");
                            String jsonStr4 = JSONUtil.toJsonStr(data4);
                            log.info("第五步请求数据：{}", jsonStr);
                            Map<String, Object> stringObjectMap4 = methodUseUtils.methodUseLogs(53l, jsonStr4);
                            log.info("第五步请求返回数据：{}", JSONUtil.toJsonStr(stringObjectMap3));
                            if (stringObjectMap4 != null && stringObjectMap4.get("org_probabilities") != null) {
                                // 将stringObjectMap4.get("org_probabilities")返回
                                String jsonStr5 = JSONUtil.toJsonStr(stringObjectMap4.get("org_probabilities"));
                                //jsonStr1 是原始的结果

                                result.put("org", org);
                                result.put("old", jsonStr1);
                                result.put("new", jsonStr5);
                                task.setStatus("2");
                                task.setAfter(jsonStr5);
                                task.setEndTime(new Date());
                                combatAtlasTaskMapper.updateCombatAtlasTask(task);
                                return result;
                            } else {
                                throw new RuntimeException("抗归属失败");

                            }

                        }

                    }


                }

            }*/

            // 抗归属前IP节点和组织风险关系 'action":"rerun analysis'
            /*OrgNode orgNodeByName = orgNodeRepository.findOrgNodeByName(request.getOrg());
            IpNode ipNodeByAddress = ipNodeRepository.findIpNodeByIp(request.getIp());
            ipNodeByAddress.setOrg(orgNodeByName);

            // 新增抗归属任务
            CombatAtlasTask task = new CombatAtlasTask();
            task.setTargetIp(request.getIp());
            task.setTaskMethod("2");
            task.setType("2");
            task.setStartTime(DateUtil.format(new Date(), "yyyy-MM-dd HH:mm:ss"));
            task.setTaskStatus("1");
            task.setBeforeRiskOrg(request.getOrg());
            combatAtlasTaskService.insertCombatAtlasTask(task);

            SysConfig sysConfig = sysConfigMapper.selectConfigById(8L);
            if ("true".equals(sysConfig.getConfigValue())) {
                // 抗归属
                List<String> ips = new ArrayList<>();
                ips.add(request.getIp());
                antiIpHomingService.predictIpHoming(ips);
            } else {

            }*/
        } catch (Exception e) {
            log.error(e.getMessage(), e);
//            throw new RuntimeException("抗定位失败");
        }
        return result;
    }


    @Override
    public Map<String, Object> riskStatistics() {
        Map<String, Object> map = new HashMap<>();
        Long totalCount = ipNodeRepository.count();
        Long belongsCount = ipNodeRepository.countByBelongsTo();
        long preCount = forecastOrgNodeRepository.count();
        map.put("totalCount", totalCount);
        map.put("belongsCount", belongsCount);
        map.put("preCount", preCount);
        return map;
    }

    @Override
    public List<OrgNode> getAllOrg() {
        List<OrgNode> all = orgNodeRepository.findAll();
        return all;
    }

    @Override
    public String combatAtlasTask(Map map) {

        try {
            if (map.get("ip") == null) {
                throw new RuntimeException("请输入ip");
            }

            CombatAtlasNewTask task = new CombatAtlasNewTask();
            task.setIp(String.valueOf(map.get("ip")));
            task.setMethod("1");
            task.setType("1");
            task.setStartTime(new Date());
            task.setBefor(String.valueOf(map.get("old_name")));

            String data = JSONUtil.toJsonStr(map);
            task.setAfter(data);
            OkHttpClient client = new OkHttpClient().newBuilder().build();
            MediaType mediaType = MediaType.parse("application/json");
            RequestBody body = RequestBody.create(mediaType, data);
            Request request = new Request.Builder()
                    .url("http://43.129.43.61:8080/start-confuse")
                    .method("POST", body)
                    .addHeader("User-Agent", "Apifox/1.0.0 (https://apifox.com)")
                    .addHeader("Content-Type", "application/json")
                    .addHeader("Authorization", "Basic YWRtaW46cGFzc3dvcmQ=")
                    .addHeader("Accept", "*/*")
                    .addHeader("Host", "43.129.43.61:8080")
                    .addHeader("Connection", "keep-alive").build();
            Response response = client.newCall(request).execute();
            int code = response.code();
            if (code != 200) {
                throw new RuntimeException("请求失败");
            }
            task.setStatus("2");
            task.setEndTime(new Date());
            combatAtlasTaskMapper.insertCombatAtlasTask(task);
        } catch (IOException e) {
            throw new RuntimeException(e.getMessage());
        }
        return "";
    }

    @Override
    public List getInfoByIp(String ip, String type) {
        String cql = "";
        if ("attackability".equals(type)) {
            cql = "MATCH path = (ip:Ip {Ip: '" + ip + "'})<-[*1..3]-(o:Org) WHERE ANY(node IN nodes(path) WHERE 'Org' IN labels(node)) RETURN ip.Ip as Ip_node, o as Org_node, [node IN nodes(path) | node] as all_nodes_in_path, [rel IN relationships(path) | rel] as all_relationships_in_path, length(path) as path_length ORDER BY path_length, o";
            Result run = neo4jConfig.run(cql);
            List<Record> list = run.list();
            List<Map> listdata = new ArrayList<>();
            list.forEach(record -> {
                List<String> keys = record.keys();
                Map<String, Object> data = new HashMap<>();
                keys.forEach(key -> {
                    if ("Ip_node".equals(key)) {
                        String string = record.get(key).asString();
                        data.put(key, string);
                    } else if ("Org_node".equals(key)) {
                        Node node = record.get(key).asNode();
                        String name = node.get("name").asString();
                        OrgNode orgNode = new OrgNode();
                        orgNode.setName(name);
                        orgNode.setId(node.id());
                        data.put(key, orgNode);
                    } else if ("all_nodes_in_path".equals(key)) {
                        List<Map> pathList = new ArrayList<>();
                        List<Node> list1 = record.get(key).asList(value -> value.asNode());
                        list1.forEach(node -> {
                            Map map = new HashMap();
                            Iterable<String> labels = node.labels();
                            map.put("labels", labels);
                            map.put("value", node.asMap());
                            map.put("id", node.id());
                            pathList.add(map);
                        });
                        data.put(key, pathList);

                    } else if ("all_relationships_in_path".equals(key)) {
                        List<Map> pathList = new ArrayList<>();
                        List<Relationship> list1 = record.get(key).asList(value -> value.asRelationship());
                        list1.forEach(node -> {
                            Map map = new HashMap();
                            map.put("type", node.type());
                            map.put("start", node.startNodeId());
                            map.put("end", node.endNodeId());
                            map.put("value", node.asMap());
                            map.put("id", node.id());
                            pathList.add(map);
                        });
                        data.put(key, pathList);

                    } else if ("path_length".equals(key)) {
                        int string = record.get(key).asInt();
                        data.put(key, string);
                    }

                });
                listdata.add(data);
            });
            return listdata;
        } else {
            cql = "MATCH (start_ip:Ip {Ip: '" + ip + "'})-[:BELONGS_TO]->(ipc:IpC) MATCH (ipc)<-[:BELONGS_TO]-(landmark_ip:Ip) WHERE landmark_ip.landmark_node = 1 MATCH path = (landmark_ip)<-[*1..3]-(o:Org) RETURN start_ip, ipc, landmark_ip, o,[node IN nodes(path) | node] as all_nodes_in_path, [rel IN relationships(path) | rel] as all_relationships_in_path, length(path) as path_length";
            Result run = neo4jConfig.run(cql);
            List<Record> list = run.list();
            List<Map> listdata = new ArrayList<>();
            list.forEach(record -> {

                List<String> keys = record.keys();
                Map<String, Object> data = new HashMap<>();
                keys.forEach(key -> {
                    if ("start_ip".equals(key)) {
                        Node node = record.get(key).asNode();
                        IpNode ipNode = new IpNode();
                        ipNode.setId(node.id());
                        ipNode.setAddress(node.get("Ip").asString());
                        data.put(key, ipNode);
                    } else if ("ipc".equals(key)) {
                        Node node = record.get(key).asNode();
                        IpcNode ipcNode = new IpcNode();
                        ipcNode.setId(node.id());
                        ipcNode.setName(node.get("IpC").asString());
                        data.put(key, ipcNode);
                    } else if ("landmark_ip".equals(key)) {
                        org.neo4j.driver.Value value = record.get(key);
                        Map map = new HashMap();
                        map.put("id", value.asNode().id());
                        map.put("labels", value.asNode().labels());
                        map.put("value", value.asNode().asMap());
                    } else if ("o".equals(key)) {
                        org.neo4j.driver.Value value = record.get(key);
                        Map map = new HashMap();
                        map.put("id", value.asNode().id());
                        map.put("labels", value.asNode().labels());
                        map.put("value", value.asNode().asMap());
                    } else if ("all_nodes_in_path".equals(key)) {
                        List<Map> pathList = new ArrayList<>();
                        List<Node> list1 = record.get(key).asList(value -> value.asNode());
                        list1.forEach(node -> {
                            Map map = new HashMap();
                            Iterable<String> labels = node.labels();
                            map.put("labels", labels);
                            map.put("value", node.asMap());
                            map.put("id", node.id());
                            pathList.add(map);
                        });
                        data.put(key, pathList);

                    } else if ("all_relationships_in_path".equals(key)) {
                        List<Map> pathList = new ArrayList<>();
                        List<Relationship> list1 = record.get(key).asList(value -> value.asRelationship());
                        list1.forEach(node -> {
                            Map map = new HashMap();
                            map.put("type", node.type());
                            map.put("start", node.startNodeId());
                            map.put("end", node.endNodeId());
                            map.put("value", node.asMap());
                            map.put("id", node.id());
                            pathList.add(map);
                        });
                        data.put(key, pathList);

                    } else if ("path_length".equals(key)) {
                        int string = record.get(key).asInt();
                        data.put(key, string);
                    }


                });
                listdata.add(data);
            });
            return listdata;
        }


    }

    public List screen() {
        String cql = "MATCH (start_ip:Ip {major: 1})-[:BELONGS_TO]->(ipc:IpC) MATCH (ipc)<-[:BELONGS_TO]-(landmark_ip:Ip) WHERE landmark_ip.landmark_node = 1 MATCH path = (landmark_ip)<-[*1..3]-(o:Org) RETURN start_ip, ipc, landmark_ip, o,[node IN nodes(path) | node] as all_nodes_in_path,[rel IN relationships(path) | rel] as all_relationships_in_path,length(path) as path_length";
        Result run = neo4jConfig.run(cql);
        List<Record> list = run.list();
        List<Map> listdata = new ArrayList<>();
        list.forEach(record -> {
            List<String> keys = record.keys();
            Map<String, Object> data = new HashMap<>();
            keys.forEach(key -> {
                if ("start_ip".equals(key)) {
                    Node node = record.get(key).asNode();
                    IpNode ipNode = new IpNode();
                    ipNode.setId(node.id());
                    ipNode.setAddress(node.get("Ip").asString());
                    data.put(key, ipNode);
                } else if ("ipc".equals(key)) {
                    Node node = record.get(key).asNode();
                    IpcNode ipcNode = new IpcNode();
                    ipcNode.setId(node.id());
                    ipcNode.setName(node.get("IpC").asString());
                    data.put(key, ipcNode);
                } else if ("landmark_ip".equals(key)) {
                    org.neo4j.driver.Value value = record.get(key);
                    Map map = new HashMap();
                    map.put("id", value.asNode().id());
                    map.put("labels", value.asNode().labels());
                    map.put("value", value.asNode().asMap());
                } else if ("o".equals(key)) {
                    org.neo4j.driver.Value value = record.get(key);
                    Map map = new HashMap();
                    map.put("id", value.asNode().id());
                    map.put("labels", value.asNode().labels());
                    map.put("value", value.asNode().asMap());
                } else if ("all_nodes_in_path".equals(key)) {
                    List<Map> pathList = new ArrayList<>();
                    List<Node> list1 = record.get(key).asList(value -> value.asNode());
                    list1.forEach(node -> {
                        Map map = new HashMap();
                        Iterable<String> labels = node.labels();
                        map.put("labels", labels);
                        map.put("value", node.asMap());
                        map.put("id", node.id());
                        pathList.add(map);
                    });
                    data.put(key, pathList);

                } else if ("all_relationships_in_path".equals(key)) {
                    List<Map> pathList = new ArrayList<>();
                    List<Relationship> list1 = record.get(key).asList(value -> value.asRelationship());
                    list1.forEach(node -> {
                        Map map = new HashMap();
                        map.put("type", node.type());
                        map.put("start", node.startNodeId());
                        map.put("end", node.endNodeId());
                        map.put("value", node.asMap());
                        map.put("id", node.id());
                        pathList.add(map);
                    });
                    data.put(key, pathList);

                } else if ("path_length".equals(key)) {
                    int string = record.get(key).asInt();
                    data.put(key, string);
                }
            });
            listdata.add(data);
        });
        return listdata;


    }

}
